package com.think.provider;

import com.think.model.User;
import com.think.service.CustomWebAuthenticationDetails;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.authentication.AuthenticationProvider;
import org.springframework.security.authentication.BadCredentialsException;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.security.crypto.bcrypt.BCrypt;
import org.springframework.stereotype.Component;

@Component
public class CustomAuthenticationProvider implements AuthenticationProvider {

    private static final Logger logger = LoggerFactory.getLogger(CustomAuthenticationProvider.class);

    @Autowired
    private UserDetailsService customUserService;

    @Override
    public Authentication authenticate(Authentication authentication) throws AuthenticationException {
        // 如上面的介绍，这里通过authentication.getDetails()获取详细信息
        CustomWebAuthenticationDetails details = (CustomWebAuthenticationDetails) authentication.getDetails();
        User user = details.getUser();
        String address = details.getRemoteAddress();
        String sessionId = details.getSessionId();
        String username = user.getUsername();
        String password = user.getPassword();
        String token = user.getToken();
        User userResult = (User) customUserService.loadUserByUsername(username);
        logger.info(username + "-" + password + "-" + token + "-" + address + "-" + sessionId);

        if(userResult == null){
            throw new BadCredentialsException("Username not found.");
        }
        //加密过程在这里体现
        boolean isMatch = BCrypt.checkpw(password, userResult.getPassword());
        if (isMatch) {
            logger.info("password is matched ");
        } else {
            throw new BadCredentialsException("Wrong password.");
        }

        // 下面是验证逻辑，验证通过则返回UsernamePasswordAuthenticationToken，
        // 否则，可直接抛出错误（AuthenticationException的子类，在登录验证不通过重定向至登录页时可通过session.SPRING_SECURITY_LAST_EXCEPTION.message获取具体错误提示信息）
        if ("123".equals(token)) {
            logger.info("token is right");
            return new UsernamePasswordAuthenticationToken(username,password,userResult.getAuthorities());
        } else {
            logger.info("token exception");
            throw new UsernameNotFoundException("token exception");
        }
    }

    @Override
    public boolean supports(Class<?> authentication) {
        return authentication.equals(UsernamePasswordAuthenticationToken.class);
    }
}